﻿using System;
using System.Net;
using System.Windows;
using System.Windows.Ink;
using System.Windows.Input;
using System.Collections.Generic;
using System.Collections.ObjectModel;
using System.Linq;
using Corina.Datamodel.Entities;
using Corina.Enumerations;
using Corina.Commands;

namespace Corina.Cydee.Apphub.Viewmodels
{
    public class PermViewmodel : ViewmodelBase
    {
        public PermViewmodel()
        {
            ManagerClient.GetAllRoleCompleted += GetAllRoleCompleted;
            CommonBaseClient.GetUserLevelAllItemsCompleted += GetUserLevelAllItemsCompleted;
            WeburlClient.GetAllTopurlCompleted += GetAllTopurlCompleted;
            WeburlClient.GetAllSuburlCompleted += GetAllSuburlCompleted;
            WeburlClient.GetTopurlPermissionCompleted += GetTopurlPermissionCompleted;
            WeburlClient.GetSuburlPermissionCompleted += GetSuburlPermissionCompleted;

            if (DataContext.IsValid)
            {
                LoadData();
                LoadUrls(PlatformTypeValue.Manager);
            }
        }

        

        #region Methods
        private void GetUserLevelAllItemsCompleted(object sender, DataService.GetUserLevelAllItemsCompletedEventArgs e)
        {
            if (e.Error == null)
            {
                if (e.Result.Result == ResultValue.Succeed)
                {
                    LevelCollection = new ObservableCollection<UserLevelInfo>(e.Result.Entities.OfType<UserLevelInfo>());
                }
            }
        }

        private void GetSuburlPermissionCompleted(object sender, DataService.GetSuburlPermissionCompletedEventArgs e)
        {
            if (e.Error == null)
            {
                if (e.Result.Result == ResultValue.Succeed)
                {
                    AccessSuburlCollection = new ObservableCollection<WeburlInfo>(e.Result.Entities.OfType<WeburlInfo>());
                }
            }
        }

        private void GetTopurlPermissionCompleted(object sender, DataService.GetTopurlPermissionCompletedEventArgs e)
        {
            if (e.Error == null)
            {
                if (e.Result.Result == ResultValue.Succeed)
                {
                    AccessTopurlCollection = new ObservableCollection<WeburlTopInfo>(e.Result.Entities.OfType<WeburlTopInfo>());
                }
            }
        }

        private void GetAllSuburlCompleted(object sender, DataService.GetAllSuburlCompletedEventArgs e)
        {
            if (e.Error == null)
            {
                if (e.Result.Result == ResultValue.Succeed)
                {
                    SuburlCollection = new ObservableCollection<WeburlInfo>(e.Result.Entities.OfType<WeburlInfo>().Where(t => !t.ShowToAll));
                    LoadSuburlPermission();
                }
            }
        }

        private void GetAllTopurlCompleted(object sender, DataService.GetAllTopurlCompletedEventArgs e)
        {
            if (e.Error == null)
            {
                if (e.Result.Result == ResultValue.Succeed)
                {
                    TopurlCollection = new ObservableCollection<WeburlTopInfo>(e.Result.Entities.OfType<WeburlTopInfo>().Where(t => !t.ShowToAll));
                }
            }
        }

        private void GetAllRoleCompleted(object sender, DataService.GetAllRoleCompletedEventArgs e)
        {
            if (e.Error == null)
            {
                if (e.Result.Result == ResultValue.Succeed)
                {
                    RolesCollection = new ObservableCollection<RoleInfo>(e.Result.Entities.OfType<RoleInfo>());
                }
            }
        }

        protected override void LoadData(params object[] paras)
        {
            ManagerClient.GetAllRoleAsync(Account, Password);
            CommonBaseClient.GetUserLevelAllItemsAsync(Account, Password);
        }

        protected void LoadUrls(PlatformTypeValue platform)
        {
            WeburlClient.GetAllTopurlAsync(Account, Password, "", platform);
        }

        protected void LoadTopurlPermission()
        {
            if (RoleOrLevelId > 0)
            {
                WeburlClient.GetTopurlPermissionAsync(Account, Password, RoleOrLevelId, SelectedAccountType);
                WeburlClient.GetAllSuburlAsync(Account, Password, "", SelectedAccountType == AccountTypeValue.Manager ? PlatformTypeValue.Manager : PlatformTypeValue.FSIM);
            }
            else
            {
                AccessTopurlCollection = new ObservableCollection<WeburlTopInfo>();
            }
        }

        protected void LoadSuburlPermission()
        {
            WeburlClient.GetSuburlPermissionAsync(Account, Password, RoleOrLevelId, SelectedAccountType);
        } 
        #endregion

        #region Properties
        private AccountTypeValue _selectedAccountType = AccountTypeValue.Manager;
        public AccountTypeValue SelectedAccountType
        {
            get { return _selectedAccountType; }
            set
            {
                _selectedAccountType = value;
                RaisePropertyChanged(() => SelectedAccountType);
                RaisePropertyChanged(() => ShowManagerCollection);
                RaisePropertyChanged(() => RoleOrLevelId);
                RaisePropertyChanged(() => SaveTopurlCommand);
                LoadTopurlPermission();
                LoadUrls(SelectedAccountType == AccountTypeValue.Manager ? PlatformTypeValue.Manager : PlatformTypeValue.FSIM);
            }
        }

        public bool ShowManagerCollection
        {
            get { return SelectedAccountType == AccountTypeValue.Manager; }
        }

        public int RoleOrLevelId
        {
            get
            {
                switch(SelectedAccountType)
                {
                    case AccountTypeValue.Manager:
                        return SelectedRole == null ? 0 : SelectedRole.Id;
                    case AccountTypeValue.User:
                        return SelectedLevel == null ? 0 : SelectedLevel.Id;
                    default: return 0;
                }
            }
        }
        #endregion

        #region Manager
        private IEnumerable<RoleInfo> _rolesCollection;
        public IEnumerable<RoleInfo> RolesCollection
        {
            get { return _rolesCollection; }
            set
            {
                _rolesCollection = value;
                RaisePropertyChanged(() => RolesCollection);
                
            }
        }

        private RoleInfo _selectedRole;
        public RoleInfo SelectedRole
        {
            get { return _selectedRole; }
            set
            {
                _selectedRole = value;
                RaisePropertyChanged(() => SelectedRole);
                RaisePropertyChanged(() => RoleOrLevelId);
                RaisePropertyChanged(() => SaveTopurlCommand);
                LoadTopurlPermission();
            }
        }
        #endregion

        #region User
        private IEnumerable<UserLevelInfo> _levelCollection;
        public IEnumerable<UserLevelInfo> LevelCollection
        {
            get { return _levelCollection; }
            set
            {
                _levelCollection = value;
                RaisePropertyChanged(() => LevelCollection);
            }
        }

        private UserLevelInfo _selectedLevel;
        public UserLevelInfo SelectedLevel
        {
            get { return _selectedLevel; }
            set
            {
                _selectedLevel = value;
                RaisePropertyChanged(() => SelectedLevel);
                RaisePropertyChanged(() => RoleOrLevelId);
                RaisePropertyChanged(() => SaveTopurlCommand);
                LoadTopurlPermission();
            }
        }
        #endregion

        #region Web
        private ObservableCollection<WeburlTopInfo> _topurlCollection;
        public ObservableCollection<WeburlTopInfo> TopurlCollection
        {
            get { return _topurlCollection; }
            set
            {
                _topurlCollection = value;
                RaisePropertyChanged(() => TopurlCollection);
                RaisePropertyChanged(() => UnselectedTopurlCollection);
            }
        }

        private ObservableCollection<WeburlTopInfo> _accessTopurlCollection;
        public ObservableCollection<WeburlTopInfo> AccessTopurlCollection
        {
            get { return _accessTopurlCollection; }
            set
            {
                _accessTopurlCollection = value;
                RaisePropertyChanged(() => AccessTopurlCollection);
                RaisePropertyChanged(() => UnselectedTopurlCollection);
            }
        }

        public IEnumerable<WeburlTopInfo> UnselectedTopurlCollection
        {
            get
            {
                return (TopurlCollection == null || AccessTopurlCollection == null) ? null : TopurlCollection.Where(t => !AccessTopurlCollection.Select(i => i.Id).Contains(t.Id));
            }
        }

        private ObservableCollection<WeburlInfo> _suburlCollection;
        public ObservableCollection<WeburlInfo> SuburlCollection
        {
            get { return _suburlCollection; }
            set
            {
                _suburlCollection = value;
                RaisePropertyChanged(() => SuburlCollection);
                RaisePropertyChanged(() => UnselectedSuburlCollection);
            }
        }

        private ObservableCollection<WeburlInfo> _accessSuburlCollection;
        public ObservableCollection<WeburlInfo> AccessSuburlCollection
        {
            get { return _accessSuburlCollection; }
            set
            {
                _accessSuburlCollection = value;
                RaisePropertyChanged(() => AccessSuburlCollection);
                RaisePropertyChanged(() => UnselectedSuburlCollection);
            }
        }

        public IEnumerable<WeburlInfo> UnselectedSuburlCollection
        {
            get
            {
                return (SuburlCollection == null || AccessSuburlCollection == null || AccessTopurlCollection == null) ? null : SuburlCollection.Where(t => AccessTopurlCollection.Select(i => i.Id).Contains(t.TopurlId)).Where(t => !AccessSuburlCollection.Select(i => i.Id).Contains(t.Id));
            }
        }
        #endregion

        #region Commands
        public ICommand MoveTopurlCommand
        {
            get
            {
                return new DelegateCommand(t =>
                {
                    int id = Convert.ToInt32(t);
                    if(AccessTopurlCollection.Select(i=>i.Id).Contains(id))
                    {
                        AccessTopurlCollection.Remove(AccessTopurlCollection.FirstOrDefault(i => i.Id == id));
                    }
                    else
                    {
                        AccessTopurlCollection.Add(UnselectedTopurlCollection.FirstOrDefault(i => i.Id == id));
                    }
                    RaisePropertyChanged(() => UnselectedTopurlCollection);
                    RaisePropertyChanged(() => AccessTopurlCollection);
                });
            }
        }

        public ICommand MoveSuburlCommand
        {
            get
            {
                return new DelegateCommand(t =>
                {
                    int id = Convert.ToInt32(t);
                    if (AccessSuburlCollection.Select(i => i.Id).Contains(id))
                    {
                        AccessSuburlCollection.Remove(AccessSuburlCollection.FirstOrDefault(i => i.Id == id));
                    }
                    else
                    {
                        AccessSuburlCollection.Add(UnselectedSuburlCollection.FirstOrDefault(i => i.Id == id));
                    }
                    RaisePropertyChanged(() => UnselectedSuburlCollection);
                    RaisePropertyChanged(() => AccessSuburlCollection);
                });
            }
        }

        public ICommand SaveTopurlCommand
        {
            get
            {
                return new GenericCommand()
                {
                    CanExecuteCallback = delegate { return RoleOrLevelId > 0; },
                    ExecuteCallback = delegate
                    {
                        WeburlClient.UpdateTopurlPermissionAsync(Account, Password, RoleOrLevelId, SelectedAccountType, string.Join(",", AccessTopurlCollection.Select(t => t.Id).ToArray()));
                    }
                };
            }
        }

        public ICommand SaveSuburlCommand
        {
            get
            {
                return new GenericCommand()
                {
                    CanExecuteCallback = delegate { return RoleOrLevelId > 0; },
                    ExecuteCallback = delegate
                    {
                        WeburlClient.UpdateSuburlPermissionAsync(Account, Password, RoleOrLevelId, SelectedAccountType, string.Join(",", AccessSuburlCollection.Select(t => t.Id).ToArray()));
                    }
                };
            }
        }

        public ICommand CancelCommand
        {
            get
            {
                return new GenericCommand()
                {
                    ExecuteCallback = delegate
                    {
                        LoadTopurlPermission();
                    }
                };
            }
        }
        #endregion
    }
}
